<template>
  <Card class="!m-10px">
    <Form :label-col="{ span: 2 }" ref="formRef" :model="attr" :rules="rules" @finish="submit">
      <!-- name指示使用哪个规则 -->
      <FormItem label="属性名" name="attrName" :wrapper-col="{ span: 4 }">
        <Input placeholder="请输入属性名" v-model:value="attr.attrName" />
      </FormItem>

      <FormItem name="attrValueList">
        <Button type="primary" :disabled="!attr.attrName" @click="showAddAttrValue">
          <template #icon><PlusOutlined /></template>
          添加属性值
        </Button>

        <Table
          :columns="columns"
          :dataSource="attr.attrValueList"
          bordered
          :pagination="false"
          class="mt-20px"
        >
          <template #bodyCell="{ index, column, text, record }">
            <template v-if="column.dataIndex === 'index'">{{ index + 1 }}</template>
            <template v-if="column.dataIndex === 'valueName'">
              <!-- 
            ref="inputRef" 所有input会共享一个ref，最终只有一个input能生效
           -->
              <Input
                placeholder="请输入属性值名称"
                :ref="(input) => (inputsRef[index] = input)"
                v-model:value="record.valueName"
                v-if="record.isShowEdit"
                @blur="addAttrValue(record, index)"
              />
              <div v-else @click="showEdit(record, index)">{{ text }}</div>
            </template>
            <template v-if="column.dataIndex === 'operator'">
              <Popconfirm title="您确认要删除当前属性值吗?" @confirm="delAttrValue(index)">
                <Button danger>
                  <template #icon><DeleteOutlined /></template>
                </Button>
              </Popconfirm>
            </template>
          </template>
        </Table>
      </FormItem>

      <FormItem>
        <!-- <Button type="primary" class="!mr-10px" @click="submit">确定</Button> -->
        <Button type="primary" class="!mr-10px" html-type="submit">确定</Button>
        <Button @click="cancel">取消</Button>
      </FormItem>
    </Form>
  </Card>
</template>

<script lang="ts">
  import { defineComponent } from 'vue';

  export default defineComponent({
    name: 'AddOrUpdateAttr',
  });
</script>

<script lang="ts" setup>
  import { ref, reactive, nextTick } from 'vue';
  import { Card, Form, FormItem, Input, Button, Table, Popconfirm, message } from 'ant-design-vue';
  import { PlusOutlined, DeleteOutlined } from '@ant-design/icons-vue';
  import { PickAttrModel } from '/@/api/product/model/attrModel';
  import { addOrUpdateAttrApi } from '/@/api/product/attr';
  import { useCategoryStore } from '/@/store/modules/category';

  const emits = defineEmits(['setIsShowAttrList']);
  const props = defineProps<{
    currentAttr: PickAttrModel;
  }>();

  const categoryStore = useCategoryStore();

  const columns = [
    {
      title: '序号',
      dataIndex: 'index',
      className: 'w-70px !text-center',
    },
    {
      title: '属性值名称',
      dataIndex: 'valueName',
    },
    {
      title: '操作',
      dataIndex: 'operator',
      className: 'w-100px',
    },
  ];
  // 表单验证规则
  const rules = {
    attrName: [{ required: true, message: '请输入属性名', trigger: 'blur' }],
    attrValueList: [{ required: true, type: 'array', message: '请至少添加一个属性值' }],
  };
  // ref获取表单组件实例对象
  const formRef = ref();
  const inputsRef = ref<HTMLInputElement[]>([]);
  // 响应式数据
  const attr = reactive<PickAttrModel>(props.currentAttr);
  /*
    1. 添加数据，显示input，同时聚焦
      push({})
      nextTick() + inputRef.value.focus()
    2. 显示模式和编辑模式的切换（收集数据）
      isShowEdit
    3. 当数据为空时，删除数据
    4. 当添加多条数据时，input怎么聚焦
      :ref='(input) => inputsRef[index] = input'
  */

  // 添加属性值按钮的回调
  const showAddAttrValue = async () => {
    // 更新是异步的
    attr.attrValueList.push({
      // 给每一个数据添加isShowEdit
      // 是否显示编辑模式
      isShowEdit: true,
      // 为了ts不报错
      valueName: '',
    });
    // 等DOM元素更新完成再触发
    await nextTick();
    // 最后一个input要聚焦
    inputsRef.value[attr.attrValueList.length - 1].focus();
  };

  // 显示编辑模式
  const showEdit = async (attrValue, index) => {
    attrValue.isShowEdit = true;
    // 问题：没有聚焦
    await nextTick();
    inputsRef.value[index].focus();
  };

  // 添加属性值
  const addAttrValue = (attrValue, index) => {
    if (!attrValue.valueName) {
      // 没有数据
      // 删除这条数据
      attr.attrValueList.splice(index, 1);
      return;
    }

    // 变成显示模式
    attrValue.isShowEdit = false;
  };

  // 删除属性值
  const delAttrValue = (index) => {
    attr.attrValueList.splice(index, 1);
  };

  /*
    1. 第一种表单校验
      formRef.value.validate();

    2. 第二种表单校验
      html-type设置按钮的原生type属性，为submit，所以是一个提交按钮
      <Button ... html-type="submit" >...</Button>
      点击按钮就会提交表单，自动触发表单校验，校验通过时触发finish事件
  */
  // const submit = async () => {
  //   await formRef.value.validate();
  //   console.log('通过');
  // };

  const submit = async () => {
    await addOrUpdateAttrApi({
      id: attr.id,
      attrName: attr.attrName,
      attrValueList: attr.attrValueList,
      categoryLevel: 3,
      categoryId: categoryStore.getCategory3Id as number,
    });
    message.success(`${attr.id ? '更新' : '添加'}属性成功`);
    cancel();
  };

  const cancel = () => {
    emits('setIsShowAttrList', true);
  };
</script>
